const got = require("got");
const Joi = require("joi");
const fse = require("fs-extra");
const qiniu = require("qiniu");
const SMSClient = require("@alicloud/sms-sdk");
const topClient = require("./lib/alidayu/topClient");
const _ = require("lodash");
const yn = require("yn");
const config = require("./config");

module.exports = {
  /**
   * 获取config配置
   */
  config(key) {
    return _.get(config, key);
  },
  isSet(name) {
    if (name != "" && name != undefined && name != "undefined") {
      return true;
    }
    return false;
  },
  // 判断是否是文件夹
  async isDir(filePath) {
    const stat = await fse.lstat(filePath);
    const isDir = stat.isDirectory();
    if (isDir) {
      return true;
    } else {
      return false;
    }
  },

  getBookshelf() {
    let bookshelf;
    if (!_.isEmpty(this.baas.connection)) {
      if (BaaS.bookshelfs[this.baas.appid]) {
        bookshelf = BaaS.bookshelfs[this.baas.appid];
      } else {
        bookshelf = BaaS.getBookshelf({
          client: "mysql",
          connection: this.baas.connection,
          pool: { min: 0, max: 1 }
        });
        BaaS.bookshelfs[this.baas.appid] = bookshelf;
      }
    }

    return bookshelf || BaaS.bookshelf;
  },
  // 判断传参是否为空，data对象，arr需要验证的key数组
  isEmpty(data, arr) {
    for (const key of arr) {
      if (_.isEmpty(_.trim(data[key]))) {
        return false;
      }
    }
    return true;
  },
  // 获取随机数
  randomCode(num) {
    let code = "";
    for (let i = 0; i < num; i++) {
      code += Math.floor(Math.random() * 10);
    }
    return code;
  },
  // 遍历查询是否有重名
  repeat(fileName, dirList) {
    for (const key in dirList) {
      if (dirList[key] == fileName) {
        return true;
      }
    }
    return false;
  },
  // 获取文件名
  async getName(fileName, type, dirPath) {
    const ctx = this;
    const dirList = await fse.readdir(dirPath);
    // 获取保存文件名
    const getNewName = await new Promise((resolve, reject) => {
      let i = 1;
      getName(fileName, fileName, type);
      function getName(fileName, orgName, type) {
        // 判断该文件夹下是否有重名文件夹，有重名则在文件夹名后加数字
        let repeat = "";
        if (type.length) {
          repeat = ctx.repeat(fileName + type, dirList);
        } else {
          repeat = ctx.repeat(fileName, dirList);
        }
        if (repeat) {
          i = fileName.replace(orgName, "");
          i = parseInt(i) ? parseInt(i) : 0;
          i++;
          fileName = orgName;
          fileName += i;
          getName(fileName, orgName, type);
        } else {
          resolve(fileName + type);
        }
      }
    });
    return getNewName;
  },
  // 遍历查询是否有重复appid
  repeatAppid(appid, appidList) {
    for (const key in appidList) {
      if (appidList[key].appid == appid) {
        return true;
      }
    }
    return false;
  },
  // 格式化内存流量
  format(flow) {
    let allFlow = 0;
    flow = flow.toUpperCase();
    if (flow.indexOf("GB") > -1) {
      allFlow += parseFloat(flow) * Math.pow(1024, 3);
    } else if (flow.indexOf("MB") > -1) {
      allFlow += parseFloat(flow) * Math.pow(1024, 2);
    } else if (flow.indexOf("KB") > -1) {
      allFlow += parseFloat(flow) * Math.pow(1024, 1);
    } else {
      allFlow += parseFloat(flow);
    }
    return allFlow ? allFlow : 0;
  },
  /**
   * 七牛图片上传
   * @param  {[type]}
   * @param  {[type]}
   * @return {[type]}
   */
  uploadFile(localFile, savename) {
    const mac = new qiniu.auth.digest.Mac(
      config.qiniu.accessKey,
      config.qiniu.secretKey
    );
    /* eslint-disable quotes */
    const options = {
      scope: config.qiniu.bucket + ":" + savename,
      returnBody:
        '{"bucket":"$(bucket)","key":"$(key)","etag":"$(etag)","fname":"$(fname)","fsize":"$(fsize)","mimeType":$(mimeType),"uuid":"$(uuid)","ext":"$(ext)"}',
      callbackBodyType: "application/json"
    };
    /* eslint-disable quotes */
    const putPolicy = new qiniu.rs.PutPolicy(options);
    const uploadToken = putPolicy.uploadToken(mac);
    const qiniuConfig = new qiniu.conf.Config();
    const formUploader = new qiniu.form_up.FormUploader(
      Object.assign(qiniuConfig, { zone: config.qiniu.zone })
    );
    const putExtra = new qiniu.form_up.PutExtra();

    return new Promise((resolve, reject) => {
      formUploader.putFile(
        uploadToken,
        savename,
        localFile,
        putExtra,
        (respErr, respBody, respInfo) => {
          if (respErr) {
            reject(respErr);
          }
          if (respInfo.statusCode == 200) {
            resolve(config.qiniu.host + respBody.key);
          } else {
            reject(respBody);
          }
        }
      );
    });
  },
  // 发送验证码，type=0验证码，type=1通知短信
  sendSms(to, code = 0, username = "", money = 0, type = 0) {
    /* eslint-disable quotes */
    const appkey = config.appkey;
    const appsecret = config.appsecret;
    const smsFreeSignName = config.sms_free_sign_name;
    let smsTemplateCode = config.sms_template_code;
    let smsParam = "";
    if (type) {
      smsParam =
        '{"name":"青否云","username":"' +
        username +
        '","money":"' +
        money +
        '"}';
      smsTemplateCode = config.sms_notice_template_code;
    } else {
      smsParam = '{"code":"' + code + '","name":"青否云"}';
    }
    /* eslint-disable quotes */
    const smsClient = new SMSClient({
      accessKeyId: appkey,
      secretAccessKey: appsecret
    });
    // 默认是阿里大于
    const TopClient = topClient.TopClient;
    const client = new TopClient({
      appkey: appkey,
      appsecret: appsecret,
      REST_URL: "http://gw.api.taobao.com/router/rest"
    });
    return new Promise((resolve, reject) => {
      client.execute(
        "alibaba.aliqin.fc.sms.num.send",
        {
          extend: "",
          sms_type: "normal",
          sms_free_sign_name: smsFreeSignName,
          sms_param: smsParam,
          rec_num: to,
          sms_template_code: smsTemplateCode
        },
        (error, response) => {
          if (error) {
            console.log("error", error);
            reject(error);
          } else {
            resolve(response);
          }
        }
      );
    });
  },

  async validate(keys = {}, schema = {}) {
    return await new Promise((resolve, reject) => {
      Joi.validate(keys, schema, (err, value) => {
        if (err) resolve(false);
        resolve(true);
      });
    });
  },
  /**
   * 获取redis键
   * @param {*} key
   */
  getVersionKey(key) {
    return `baas:${config.version}:${key}`;
  },
  /**
   * 获取应用redis键
   * @param {*} key
   * @param {*} ignoreDev 忽略开发者
   */
  getAppKey(key, appid, appkey) {
    // 开发者模式，不缓存redis
    if (yn(this.dev) && !ignoreDev) {
      return "";
    }
    return this.getVersionKey.bind(this)(
      `appid:${appid}:appkey:${appkey}:${key}`
    );
  },
  success(data, msg, meta) {
    this.body = { data, msg, code: 1, meta };
  },
  error(data, msg, meta) {
    this.body = { data, msg, code: 0, meta };
  }
};
